package com.xrui.hbaseview.data;

import com.univocity.parsers.csv.CsvWriter;
import com.univocity.parsers.csv.CsvWriterSettings;
import com.xrui.hbaseview.hbase.Connection;

import java.io.ByteArrayOutputStream;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.util.ArrayList;
import java.util.List;

/**
 * This class represents a grid or an hbase table. The class' primary usage is a copy/paste operations.
 */
public class DataTable {

    //region Variables
    /**
     * The name of the table.
     */
    private String tableName;
    /**
     * This class is used to access the hbase.
     */
    private Connection connection;
    /**
     * The list of rows that belong to the table.
     */
    private List<DataRow> rows;
    //endregion

    //region Constructor

    /**
     * Initializes a new instance of the {@link DataTable} class.
     *
     * @param tableName The name of the table.
     */
    public DataTable(String tableName) {
        this(tableName, null);
    }

    /**
     * Initializes a new instance of the {@link DataTable} class.
     *
     * @param tableName  The name of the table.
     * @param connection The reference to an hbase helper.
     */
    public DataTable(String tableName, Connection connection) {
        this.tableName = tableName;
        this.connection = connection;
        this.rows = new ArrayList<>();
    }
    //endregion

    //region Public Properties

    /**
     * Gets the name of the table.
     *
     * @return The name of the table.
     */
    public String getTableName() {
        return this.tableName;
    }

    /**
     * Sets a new table name.
     *
     * @param tableName A new table name.
     */
    public void setTableName(String tableName) {
        this.tableName = tableName;
    }

    /**
     * Gets a reference to the {@link Connection} class that was used to load the data from hbase.
     *
     * @return The reference to the hbase helper.
     */
    public Connection getConnection() {
        return this.connection;
    }

    /**
     * Adds a row to the table.
     *
     * @param row The row to add.
     */
    public void addRow(DataRow row) {
        this.rows.add(row);
    }

    /**
     * Removes the row from the table.
     *
     * @param row The row to remove.
     */
    public void removeRow(DataRow row) {
        this.rows.remove(row);
    }

    /**
     * Gets a collection of all table rows.
     *
     * @return A list of row if there are any or an empty collection.
     */
    public Iterable<DataRow> getRows() {
        return this.rows;
    }

    /**
     * Gets the number of rows in the table.
     *
     * @return A number of rows in the table.
     */
    public int getRowsCount() {
        return this.rows.size();
    }

    @Override
    public String toString() {
        CsvWriterSettings csvWriterSettings = new CsvWriterSettings();
        csvWriterSettings.setHeaderWritingEnabled(true);
        // Writing to an in-memory byte array. This will be printed out to the standard output so you can easily see the result.
        ByteArrayOutputStream csvResult = new ByteArrayOutputStream();
        // CsvWriter (and all other file writers) work with an instance of java.io.Writer
        Writer outputWriter = new OutputStreamWriter(csvResult);
        // Creates a writer with the above settings;
        CsvWriter writer = new CsvWriter(outputWriter, csvWriterSettings);
        for(DataRow row : rows) {
            writer.writeRow(row.toMap());
        }
        writer.close();

        return csvResult.toString();
    }

    //endregion
}
